    // Copyright (C) 1953-2023 NUDT
// Verilog module name - forward_mode_judge
// Version: V3.2.0.20210722
// Created:
//         by - fenglin 
////////////////////////////////////////////////////////////////////////////
// Description:
//          
///////////////////////////////////////////////////////////////////////////

`timescale 1ns/1ps

module forward_mode_judge
(
        i_clk,
        i_rst_n,
              
        iv_desp     ,  
        i_desp_wr   ,  
                    
        iv_ram_rdata  ,
                    
        ov_desp_storedfwd       ,
        o_desp_wr_storedfwd     ,
        o_cutthroughfwd         ,
        ov_pkt_inport           ,
        
        ov_desp_cutthroughfwd   ,
        o_desp_wr_cutthroughfwd    
);

// I/O
// clk & rst
input                  i_clk;                   //125Mhz
input                  i_rst_n;
// pkt_bufid and pkt_type and outport from lookup_table
input      [87:0]      iv_desp;
input                  i_desp_wr;
// pkt_bufid and pkt_type to p0
output reg [87:0]      ov_desp_storedfwd;
output reg             o_desp_wr_storedfwd;
output reg             o_cutthroughfwd    ;
output reg [5:0]       ov_pkt_inport      ;

output reg [87:0]      ov_desp_cutthroughfwd  ;
output reg             o_desp_wr_cutthroughfwd;
//read data from RAM
input      [33:0]      iv_ram_rdata;
//////////////////////////////////////////////////
//              forward                         //
//////////////////////////////////////////////////
always @(posedge i_clk or negedge i_rst_n) begin
    if(i_rst_n == 1'b0)begin
        ov_desp_storedfwd                <= 88'h0 ;
        o_desp_wr_storedfwd              <= 1'h0  ;
        o_cutthroughfwd                  <= 1'b0  ;
        ov_pkt_inport                    <= 6'b0  ;
        
        ov_desp_cutthroughfwd            <= 88'h0 ;
        o_desp_wr_cutthroughfwd          <= 1'h0  ;
        
    end                              
    else begin
        if(i_desp_wr == 1'b1)begin
            if(iv_ram_rdata[33])begin//valid
                //if(|(iv_ram_rdata[32:0] & iv_desp[86:54]) == 1'b1)begin//存储式转发；只要该描述符有某�?个输出端口为存储式转发，则所有输出端口均为存储式转发�?
                if(|({iv_ram_rdata[32],iv_ram_rdata[3:0]} & {iv_desp[86],iv_desp[57:54]}) == 1'b1)begin//存储式转发；只要该描述符有某丿个输出端口为存储式转发，则所有输出端口均为存储式转发〿    
                    ov_desp_storedfwd         <= iv_desp;
                    o_desp_wr_storedfwd       <= i_desp_wr;
                    o_cutthroughfwd           <= 1'b0  ;
                    ov_pkt_inport             <= iv_desp[42:37];                    
                    
                    ov_desp_cutthroughfwd     <= 88'h0 ;
                    o_desp_wr_cutthroughfwd   <= 1'h0  ;                    
                end
                else begin
                    ov_desp_storedfwd                <= 88'h0 ;
                    o_desp_wr_storedfwd              <= 1'h1  ;
                    o_cutthroughfwd                  <= 1'b1;
                    ov_pkt_inport                    <= iv_desp[42:37];
                    
                    ov_desp_cutthroughfwd            <= iv_desp;
                    o_desp_wr_cutthroughfwd          <= i_desp_wr;
                end
            end
            else begin//invalid
                ov_desp_storedfwd         <= iv_desp;
                o_desp_wr_storedfwd       <= i_desp_wr;
                o_cutthroughfwd           <= 1'b0  ;
                ov_pkt_inport             <= iv_desp[42:37];        
                
                ov_desp_cutthroughfwd     <= 88'h0 ;
                o_desp_wr_cutthroughfwd   <= 1'h0  ;  
            end
        end
        else begin
            ov_desp_storedfwd                <= 88'h0 ;
            o_desp_wr_storedfwd              <= 1'h0  ;
            o_cutthroughfwd           <= 1'b0  ;
            ov_pkt_inport             <= 6'b0  ;              
            
            ov_desp_cutthroughfwd            <= 88'h0 ;
            o_desp_wr_cutthroughfwd          <= 1'h0  ;
        end
    end
end
endmodule
